package com.tong.embeddedvr.service.impl;

import com.tong.embeddedvr.Mapper.HomeworkMapper;
import com.tong.embeddedvr.dto.*;
import com.tong.embeddedvr.entity.CollectionEntity;
import com.tong.embeddedvr.entity.HomeworkEntity;
import com.tong.embeddedvr.entity.UserEntity;
import com.tong.embeddedvr.service.HomeworkService;
import com.tong.embeddedvr.utils.CommonUtil;
import ma.glasnost.orika.impl.DefaultMapperFactory;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.multipart.commons.CommonsMultipartFile;

import javax.servlet.ServletOutputStream;
import javax.servlet.http.HttpServletRequest;
import javax.servlet.http.HttpServletResponse;
import java.io.*;
import java.text.SimpleDateFormat;
import java.util.Date;
import java.util.List;
import java.util.UUID;

/**
 * TODO
 *
 * @author gcl
 * @version 1.0
 * @Description
 * @date 2020/12/28 19:51
 */
@Service
public class HomeworkServiceImpl implements HomeworkService {

    @Autowired
    HomeworkMapper homeworkMapper;

    private Logger logger = LoggerFactory.getLogger(HomeworkServiceImpl.class);

    @Override
    public String fileUpload(HttpServletRequest request, CommonsMultipartFile file) {
        //获取文件名 : file.getOriginalFilename();
        String uploadFileName = file.getOriginalFilename();
        UUID randomUUID = UUID.randomUUID();
        String suffixName = uploadFileName.substring(uploadFileName.lastIndexOf("."));
        String newName = randomUUID+suffixName;
        String res = null;

        //如果文件名为空，返回错误消息
        if ("".equals(uploadFileName)){
            return CommonUtil.ajaxReturn(400,"文件名为空,上传失败");
        }

        //上传路径保存设置
        SimpleDateFormat sdf = new SimpleDateFormat("yyyyMMdd");
        String date = sdf.format(new Date());
        String path = request.getServletContext().getRealPath("/" + date);  //文件夹下绝对路径upload
        //如果路径不存在，创建一个
        File realPath = new File(path);
        if (!realPath.exists()){
            realPath.mkdir();
        }
        logger.info("文件存储路径:[{}]",realPath);
        try{
            InputStream is = file.getInputStream(); //文件输入流
            OutputStream os = new FileOutputStream(new File(realPath,newName)); //文件输出流

            //读取写出
            int len=0;
            byte[] buffer = new byte[1024];
            while ((len=is.read(buffer))!=-1){
                os.write(buffer,0,len);
                os.flush();
            }
            os.close();
            is.close();

            String filePath = realPath + "\\" + newName;

            res = CommonUtil.ajaxReturn(filePath);
        }catch (Exception e){
            e.printStackTrace();
            res = CommonUtil.ajaxReturn(400,"上传失败,请稍后重试!");
        }
        return res;
    }

    @Override
    public void fileDownload(HttpServletResponse resp,HomeworkDTO homeworkDTO) {
        try{
            //1. 获取下载文件的路径
            DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
            HomeworkEntity prop = mapperFactory.getMapperFacade().map(homeworkDTO, HomeworkEntity.class);
            HomeworkDTO homeworkDTO1 = homeworkMapper.selectHomeworkById(prop);
            String filePath = homeworkDTO1.getHomeworkFileAddress();
            //2. 获取下载的文件名
            String fileName = filePath.substring(filePath.lastIndexOf("\\")+1);
            //3. 设置浏览器响应下载文件
            resp.setHeader("Content-Disposition","attachment;filename="+fileName);
            //4. 获取下载文件的输入流
            FileInputStream in = new FileInputStream(filePath);
            //5. 创建缓冲区
            int len=0;
            byte[] buffer = new byte[2014];
            //6. 获取OutputStream对象
            ServletOutputStream out = resp.getOutputStream();
            //7. 将FileOutputStream流写入到buffer缓冲区,使用OutputStream将缓冲区中的数据输出到客户端
            while((len=in.read(buffer))>0){
                out.write(buffer,0,len);
            }
            in.close();
            out.close();
        }catch (Exception e){
            e.printStackTrace();
        }
    }

    //这里不需要加事务,因为只有一个增加或修改操作
    @Override
    public Integer submitHomework(HomeworkDTO homeworkDTO,CollectionDTO collectionDTO) throws Exception {
        logger.info("正在尝试提交作业|homework:[{}],collection:[{}]",homeworkDTO,collectionDTO);
        DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
        HomeworkEntity prop = mapperFactory.getMapperFacade().map(homeworkDTO, HomeworkEntity.class);
        CollectionEntity collectionEntity = mapperFactory.getMapperFacade().map(collectionDTO, CollectionEntity.class);
        Integer res = 0;
        SimpleDateFormat sdf = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
        String nowTime = CommonUtil.getTime();
        Date now = sdf.parse(nowTime);
        Date endTime = sdf.parse(collectionEntity.getCollectionEndTime());
        if(now.getTime() < endTime.getTime()){
            //需要增加的homework,state均置为1
            if(prop.getHomeworkId()==null){  //没有则新增
                //先检验是否有重复的项
                HomeworkDTO homework = homeworkMapper.selectHomeworkByUserIdAndCollectionId(prop);
                if(homework==null){
                    prop.setHomeworkState(0);
                    prop.setHomeworkCreateTime(nowTime);
                    prop.setHomeworkSubmitTime(nowTime);
                    homeworkMapper.homeworkAdd(prop);
                    //第一次找不到,第二次总能找到的
                    res = homeworkMapper.selectHomeworkByUserIdAndCollectionId(prop).getHomeworkId();
                }else{
                    res = homeworkDTO.getHomeworkId();
                }
            }
            else if(prop.getHomeworkState()==0){  //更新
                //保存
                prop.setHomeworkSubmitTime(nowTime);
                homeworkMapper.updateHomework(prop);
                res = prop.getHomeworkId();
            }else {
                res = 0;
            }
        }else if(prop.getHomeworkState()==2){  //打回修改
            //修订
            prop.setHomeworkState(0);  //更新为提交状态0并等待修改
            prop.setHomeworkSubmitTime(nowTime);
            homeworkMapper.updateHomework(prop);
            res = prop.getHomeworkId();
        }else{
            res = 0;
        }
        return res;
    }

    @Transactional(rollbackFor = Exception.class)
    @Override
    public TableRspDTO showTable(TableReqDTO tableReqDTO, CollectionDTO collectionDTO) throws Exception {
        DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
        CollectionEntity prop = mapperFactory.getMapperFacade().map(collectionDTO, CollectionEntity.class);
        List<HomeworkDTO> homeworkDTOList = homeworkMapper.selectTableByCollectionId(tableReqDTO.getQueryText(),tableReqDTO.getStart(),tableReqDTO.getPageSize(), prop);
        Integer count = homeworkMapper.selectCountByCollectionId(tableReqDTO.getQueryText(), prop);
        TableRspDTO res = new TableRspDTO();
        res.setTotal(count);
        res.setListTable(homeworkDTOList);
        return res;
    }

    //只有在更新操作时才需要rollback
    @Override
    public TableRspDTO showTable(TableReqDTO tableReqDTO, UserInputDTO userInputDTO) throws Exception {
        DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
        UserEntity prop = mapperFactory.getMapperFacade().map(userInputDTO, UserEntity.class);
        List<HomeworkDTO> homeworkDTOList = homeworkMapper.selectTableByUserId(tableReqDTO.getQueryText(), tableReqDTO.getStart(), tableReqDTO.getPageSize(), prop);
        Integer count = homeworkMapper.selectCountByUserId(tableReqDTO.getQueryText(), prop);
        TableRspDTO res = new TableRspDTO();
        res.setListTable(homeworkDTOList);
        res.setTotal(count);
        return res;
    }

    @Override
    public HomeworkDTO showHomework(HomeworkDTO homeworkDTO) throws Exception {
        DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
        HomeworkEntity prop = mapperFactory.getMapperFacade().map(homeworkDTO, HomeworkEntity.class);
        HomeworkDTO res = homeworkMapper.selectHomeworkById(prop);
        return res;
    }

    @Override
    @Transactional(rollbackFor = Exception.class)
    public Integer evaluate(HomeworkDTO homeworkDTO) throws Exception {
        DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
        HomeworkEntity prop = mapperFactory.getMapperFacade().map(homeworkDTO, HomeworkEntity.class);
        Integer res = 0;
        if((prop.getHomeworkState()==1)&&prop.getHomeworkEvaluate()!=null&prop.getHomeworkGrade()!=null){
            res = homeworkMapper.updateHomework(prop);
        }else{
            res = 0;
        }
        return res;
    }

    @Override
    public String showHomeworkByUserIdAndCollectionId(HomeworkDTO homeworkDTO) {
        String res = null;
        DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
        HomeworkEntity prop = mapperFactory.getMapperFacade().map(homeworkDTO, HomeworkEntity.class);
        HomeworkDTO homeworkDTO1 = homeworkMapper.selectHomeworkByUserIdAndCollectionId(prop);
        if(res!=null){
            res = CommonUtil.ajaxReturn(homeworkDTO1);
        }else{
            res = CommonUtil.ajaxReturn(300,"该作业无提交记录");  //300表示输出结果不需要像用户通报
        }
        return res;
    }

    @Override
    public String delHomework(HomeworkDTO homeworkDTO) {
        String res = null;
        DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
        HomeworkEntity prop = mapperFactory.getMapperFacade().map(homeworkDTO, HomeworkEntity.class);
        prop.setHomeworkIsDelete(1);
        try {
            homeworkMapper.updateHomework(prop);
            res = CommonUtil.ajaxReturn("删除成功");
        } catch (Exception e) {
            logger.error("作业删除失败:[{}]",homeworkDTO);
            e.printStackTrace();
            res = CommonUtil.ajaxReturn(500,"作业删除失败!");
        }
        return res;
    }

    @Override
    public Integer updatedHomework(HomeworkDTO homeworkDTO) throws Exception {
        DefaultMapperFactory mapperFactory = CommonUtil.getMapperFactory();
        HomeworkEntity prop = mapperFactory.getMapperFacade().map(homeworkDTO, HomeworkEntity.class);
        String nowTime = CommonUtil.getTime();
        prop.setHomeworkSubmitTime(nowTime);
        Integer res = homeworkMapper.updateHomework(prop);
        return res;
    }
}
